format ELF64 executable 3
entry start

include 'import64.inc'
interpreter '/lib64/ld-linux-x86-64.so.2'
needed 'libdl.so.2'
import dlopen, dlsym

macro emit [param] { param }

DEBUG = 0

segment readable executable

start:
    sub rsp,128
    emit < platform_id equ rsp >,< device_id equ rsp+8 >,< printf equ rsp+16 >
if DEBUG = 1
    ; load printf
    emit < mov rdi,rax >,< mov rsi,g_str_printf >,< call [dlsym] >,< mov [printf],rax >
end if
    ; load OpenCL
    emit < mov rdi,g_str_libopencl >,< mov esi,1 >,< call [dlopen] >,< mov r12,rax >
    ; call clGetPlatformIDs
    emit < mov rdi,r12 >,< mov rsi,g_str_clGetPlatformIDs >,< call [dlsym] >
    emit < mov edi,1 >,< lea rsi,[platform_id] >,< xor edx,edx >,< call rax >
    ; call clGetDeviceIDs
    emit < mov rdi,r12 >,< mov rsi,g_str_clGetDeviceIDs >,< call [dlsym] >
    emit < mov rdi,[platform_id] >,< mov esi,1 >< mov edx,1 >,< lea rcx,[device_id] >,< xor r8d,r8d >,< call rax >
    ; call clCreateContext
    emit < mov rdi,r12 >,< mov rsi,g_str_clCreateContext >,< call [dlsym] >
    emit < xor edi,edi >,< mov esi,1 >,< lea rdx,[device_id] >< xor ecx,ecx >,< xor r8d,r8d >,< xor r8d,r9d >,< call rax >,< mov r13,rax >
    ; load clReleaseContext
    mov rdi, r12
    mov rsi, g_str_clReleaseContext
    call [dlsym]
    ; call clReleaseContext
    mov rdi, r13
    call rax
if DEBUG = 1
    ; print
    mov rdi, g_str_p
    mov rsi, rax
    call [printf]
end if
    ; terminate process
    mov eax,60
    mov edi,0
    syscall

g_str_libopencl db 'libOpenCL.so.1',0
g_str_clGetPlatformIDs db 'clGetPlatformIDs',0
g_str_clGetDeviceIDs db 'clGetDeviceIDs',0
g_str_clCreateContext db 'clCreateContext',0
g_str_clReleaseContext db 'clReleaseContext',0
if DEBUG = 1
g_str_printf db 'printf',0
g_str_d db '%d',10,0
g_str_p db '%p',10,0
end if

;align 8
;g_errcode_ret dq 0
